#include "CButton.h"

CButton::CButton() :upStatus(NULL), downStatus(NULL), currentStatus(NULL), _status(BUTTON_STATUS_NONE), listener(NULL), pszButtonName(NULL)
{
	
}

CButton::~CButton()
{
	_eventDispatcher->removeEventListener(listener);
	CC_SAFE_RELEASE_NULL(listener);

	_status = BUTTON_STATUS_NONE;
	currentStatus = NULL;
	CC_SAFE_RELEASE_NULL(upStatus);
	CC_SAFE_RELEASE_NULL(downStatus);
}

CButton* CButton::create(const char* pszUpFileName, const char* pszDownFileName /*= NULL*/)
{
	CButton* button = new CButton();
	if (button && button->init())
	{
		button->autorelease();
		button->setUpFile(pszUpFileName);
		button->setDownFile(pszDownFileName);
		button->setStatus(BUTTON_STATUS_UP);
		return button;
	}
	else
	{
		delete button;
		button = NULL;
	}
	return NULL;
}

void CButton::setStatus(EnumButtonStatus status)
{
	_status = status;
	removeAllChildren();
	currentStatus = NULL;
	switch (_status)
	{
	case BUTTON_STATUS_UP:
		currentStatus = upStatus;
		currentStatus->setScale(1.0f);
		break;
	case BUTTON_STATUS_DOWN:
		if (downStatus)
		{
			currentStatus = downStatus;
		}
		else
		{
			currentStatus = upStatus;
			currentStatus->setScale(0.9f);
		}
		break;
	case BUTTON_STATUS_SELECTED:
		break;
	default:
		break;
	}
	if (currentStatus)
	{
		addChild(currentStatus);
	}
}

EnumButtonStatus CButton::getStatus()
{
	return _status;
}

void CButton::setUpFile(const char* pszFileName)
{
	CCAssert(pszFileName != NULL, "up status filename can not be null");
	upStatus = CCSprite::create(pszFileName);
	upStatus->retain();
}

void CButton::setDownFile(const char* pszFileName)
{
	if (pszFileName != NULL)
	{
		downStatus = CCSprite::create(pszFileName);
		downStatus->retain();
	}
}

bool CButton::checkTouchInside(CCTouch *pTouch)
{
	if (currentStatus)
	{
		CCPoint pos = currentStatus->getPosition();
		CCSize size = currentStatus->getContentSize();
		CCRect rect = CCRectMake(pos.x - size.width / 2, pos.y - size.height / 2, size.width, size.height);
		CCPoint touchPoint = convertTouchToNodeSpaceAR(pTouch);
		return rect.containsPoint(touchPoint);
	}
	return false;
}

bool CButton::init()
{
	if (!CCSprite::init())
	{
		return false;
	}
	listener = EventListenerTouchOneByOne::create();
	listener->retain();
	listener->setSwallowTouches(true);
	listener->onTouchBegan = [this](CCTouch *pTouch, CCEvent *pEvent)
	{
		if (checkTouchInside(pTouch))
		{
			CCLOG("%s button pressed", pszButtonName);
			setStatus(BUTTON_STATUS_DOWN);
			return true;
		}
		return false;
	};
	listener->onTouchEnded = [this](CCTouch *pTouch, CCEvent *pEvent)
	{
		if (checkTouchInside(pTouch))
		{
			CCLOG("%s button released", pszButtonName);
			CCNotificationCenter::sharedNotificationCenter()->postNotification(BUTTON_CLICK_EVENT, this);
		}
		setStatus(BUTTON_STATUS_UP);
	};
	_eventDispatcher->addEventListenerWithSceneGraphPriority(listener, this);
	return true;
}
